﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using BussinessLogic.Models;
using BussinessLogic.Services;
using BussinessLogic.Helpers;
using System.Web.Security;
using BussinessLogic.Models.Administrator;
using Newtonsoft.Json;

namespace AspMVCProject.Controllers
{
    [Authorize]
    public class AdministratorController : Controller
    {
        public ActionResult Index()
        {
            if (!AccountService.IsUserInRole(User.Identity.Name, AccountService.UserRole.Administrator))
            {
                return RedirectToAction("LogOn", "Account");
            }

            List<UserInfo> users = AccountService.GetUsers();
            return View(users);
        }

        public ActionResult CreateAdministrator()
        {
            if (!AccountService.IsUserInRole(User.Identity.Name, AccountService.UserRole.Administrator))
            {
                return RedirectToAction("LogOn", "Account");
            }

            return View();
        }

        [HttpPost]
        public ActionResult CreateAdministrator(CreateAdminModel model)
        {
            if (!AccountService.IsUserInRole(User.Identity.Name, AccountService.UserRole.Administrator))
            {
                return RedirectToAction("LogOn", "Account");
            }

            if (ModelState.IsValid)
            {
                // Attempt to register the user
                Guid? activationHash = AccountService.RegisterAdmin(model);

                if (activationHash != null)
                {
                    EmailHelper.SendCreatAdminEmail(model.Email, string.Empty, activationHash);
                    return RedirectToAction("Index");
                }
                else
                {
                    ModelState.AddModelError("", ErrorCodeToString(MembershipCreateStatus.DuplicateUserName));
                }
            }
            return View();
        }

        [HttpPost]
        public ActionResult ApproveUserToSudy(int studyId, int userId)
        {
            if (!AccountService.IsUserInRole(User.Identity.Name, AccountService.UserRole.Administrator))
            {
                return RedirectToAction("LogOn", "Account");
            }

            StudyServices.ApproveUserToSudy(studyId, userId);
            return View();
        }

        public ActionResult ListAccounts()
        {
            if (!AccountService.IsUserInRole(User.Identity.Name, AccountService.UserRole.Administrator))
            {
                return RedirectToAction("LogOn", "Account");
            }

            List<LockAccountModel> accounts = AccountService.GetAllActiveUsers();
            return View(accounts);
        }

        public ActionResult LockAccount(int id)
        {
            if (!AccountService.IsUserInRole(User.Identity.Name, AccountService.UserRole.Administrator))
            {
                return RedirectToAction("LogOn", "Account");
            }

            AccountService.LockAccount(id);
            return RedirectToAction("Index");
        }

        public ActionResult UnlockAccount(int id)
        {
            if (!AccountService.IsUserInRole(User.Identity.Name, AccountService.UserRole.Administrator))
            {
                return RedirectToAction("LogOn", "Account");
            }

            AccountService.UnlockAccount(id);
            return RedirectToAction("Index");
        }

        public ActionResult Users()
        {
            List<UserInfo> users = AccountService.GetUsers();
            return View(users);
        }

        public ActionResult UserDetails(int id)
        {
            UserDetails ud = AccountService.GetUserInfo(id);

            return View(ud);
        }

        public ActionResult UserStudyDetails(int sid, int uid)
        {
            UserStudyDetails usd = AccountService.GetUserStudyDetails(sid, uid);

            return View(usd);
        }

        public ActionResult UserSessionDetails(int? id, bool? initial, int? sid, int? uid)
        {
            List<SessionExercise> sessionDetails;
            if (initial != null && (bool)initial)
            {
                sessionDetails = SessionService.GetUserSessionDetails(null, sid, uid);
            }
            else
            {
                sessionDetails = SessionService.GetUserSessionDetails(id, null, null);
            }

            return View(sessionDetails);
        }

        [HttpPost]
        public ActionResult SaveScore(string result)
        {
            var res = JsonConvert.DeserializeObject<List<SaveScore>>(result);

            SessionService.SaveScore(res);

            return View();
        }



        #region Status Codes
        private static string ErrorCodeToString(MembershipCreateStatus createStatus)
        {
            // See http://go.microsoft.com/fwlink/?LinkID=177550 for
            // a full list of status codes.
            switch (createStatus)
            {
                case MembershipCreateStatus.DuplicateUserName:
                    return "User name already exists. Please enter a different user name.";

                case MembershipCreateStatus.DuplicateEmail:
                    return "A user name for that e-mail address already exists. Please enter a different e-mail address.";

                case MembershipCreateStatus.InvalidPassword:
                    return "The password provided is invalid. Please enter a valid password value.";

                case MembershipCreateStatus.InvalidEmail:
                    return "The e-mail address provided is invalid. Please check the value and try again.";

                case MembershipCreateStatus.InvalidAnswer:
                    return "The password retrieval answer provided is invalid. Please check the value and try again.";

                case MembershipCreateStatus.InvalidQuestion:
                    return "The password retrieval question provided is invalid. Please check the value and try again.";

                case MembershipCreateStatus.InvalidUserName:
                    return "The user name provided is invalid. Please check the value and try again.";

                case MembershipCreateStatus.ProviderError:
                    return "The authentication provider returned an error. Please verify your entry and try again. If the problem persists, please contact your system administrator.";

                case MembershipCreateStatus.UserRejected:
                    return "The user creation request has been canceled. Please verify your entry and try again. If the problem persists, please contact your system administrator.";

                default:
                    return "An unknown error occurred. Please verify your entry and try again. If the problem persists, please contact your system administrator.";
            }
        }
        #endregion
    }
}
